/*
 * Copyright 2014-2026 the original author or authors.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package com.wzq.util;

import java.util.Map;

import javax.annotation.PostConstruct;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.io.IOUtils;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;


/**
 */
public class ApiSignHttpRequestInterceptor extends HandlerInterceptorAdapter {
	protected final Logger logger = LogManager.getLogger(getClass());
	@Value("${app.api.skipSign:false}")
	private boolean skipSign;
	@Value("${app.api.key:db426a9829e4b49a0dcac7b4162da6b6}")
	private String key;

	@PostConstruct
	public void init() {
		logger.info("跳过签名={}， key={}", skipSign, key);
	}

	@Override
	public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
			throws Exception {
		if (skipSign || isSignOk(request, handler))
			return super.preHandle(request, response, handler);
		response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
		response.setContentType("application/json;charset=UTF-8");

			@SuppressWarnings("rawtypes")
			ApiResponse spiResponse = new ApiResponse(ResponseCode.SIGN_ERR);
			response.getOutputStream().write(UtilJson.writeValueAsString(spiResponse).getBytes(UtilIo.utf8));
		
		return false;
	}

	private boolean isSignOk(HttpServletRequest request, Object handler) throws Exception {
		boolean result = false;
		HandlerMethod method = (HandlerMethod) handler;
		RequestBody requestBody = null;
		if (method.getMethod().getParameters() != null && method.getMethod().getParameters().length > 0) {
			requestBody = method.getMethod().getParameters()[0].getAnnotation(RequestBody.class);
		}
		if (requestBody != null) {// 如果是post json请求
			String json = IOUtils.toString(request.getInputStream());
			result = UtilSign.signJson(key, json, request.getRequestURI());
		} else {
			String reqSign = request.getParameter("sign");
			if (UtilString.isEmpty(reqSign) || reqSign.length() != UtilString.md5Len) {
				logger.debug("签名错误 request.sign={}, url={}", reqSign, request.getRequestURI());
				return false;
			}
			Map<String, String[]> params = request.getParameterMap();
			String sign = UtilSign.sign(key, params);
			result = reqSign.equalsIgnoreCase(sign);
			logger.debug("签名={}, request.sign={}, sign={}, url={}, params={}", result, reqSign, sign,
					request.getRequestURI(), params);
		}
		return result;
	}

}
